import { COLORS, BOARD_CONFIG, INITIAL_POSITIONS } from './constants.js';
import { createPiece } from './pieces.js';

// 棋盘类
export class Board {
    constructor() {
        this.reset();
    }
    
    // 重置棋盘
    reset() {
        this.grid = Array(BOARD_CONFIG.ROWS).fill(null)
            .map(() => Array(BOARD_CONFIG.COLS).fill(null));
        this.moveHistory = [];
        this.setupInitialPieces();
    }
    
    // 设置初始棋子位置
    setupInitialPieces() {
        // 添加红方棋子
        INITIAL_POSITIONS[COLORS.RED].forEach(pos => {
            const piece = createPiece(pos.type, COLORS.RED, pos.row, pos.col);
            this.grid[pos.row][pos.col] = piece;
        });
        
        // 添加黑方棋子
        INITIAL_POSITIONS[COLORS.BLACK].forEach(pos => {
            const piece = createPiece(pos.type, COLORS.BLACK, pos.row, pos.col);
            this.grid[pos.row][pos.col] = piece;
        });
    }
    
    // 获取指定位置的棋子
    getPieceAt(row, col) {
        if (row < 0 || row >= BOARD_CONFIG.ROWS || col < 0 || col >= BOARD_CONFIG.COLS) {
            return null;
        }
        return this.grid[row][col];
    }
    
    // 设置指定位置的棋子
    setPieceAt(row, col, piece) {
        if (row >= 0 && row < BOARD_CONFIG.ROWS && col >= 0 && col < BOARD_CONFIG.COLS) {
            this.grid[row][col] = piece;
            if (piece) {
                piece.row = row;
                piece.col = col;
            }
        }
    }
    
    // 移动棋子
    movePiece(fromRow, fromCol, toRow, toCol) {
        const piece = this.getPieceAt(fromRow, fromCol);
        if (!piece) {
            return null;
        }
        
        // 检查移动是否合法
        if (!piece.isValidMove(this, toRow, toCol)) {
            return null;
        }
        
        // 保存被吃掉的棋子
        const capturedPiece = this.getPieceAt(toRow, toCol);
        
        // 记录移动历史
        this.moveHistory.push({
            fromRow,
            fromCol,
            toRow,
            toCol,
            piece,
            capturedPiece
        });
        
        // 执行移动
        this.setPieceAt(fromRow, fromCol, null);
        this.setPieceAt(toRow, toCol, piece);
        piece.hasMoved = true;
        
        return capturedPiece;
    }
    
    // 撤销上一步移动
    undoMove() {
        if (this.moveHistory.length === 0) {
            return false;
        }
        
        const move = this.moveHistory.pop();
        this.setPieceAt(move.fromRow, move.fromCol, move.piece);
        this.setPieceAt(move.toRow, move.toCol, move.capturedPiece);
        
        return true;
    }
    
    // 查找将/帅
    findGeneral(color) {
        for (let row = 0; row < BOARD_CONFIG.ROWS; row++) {
            for (let col = 0; col < BOARD_CONFIG.COLS; col++) {
                const piece = this.getPieceAt(row, col);
                if (piece && piece.color === color && piece.type === 'general') {
                    return piece;
                }
            }
        }
        return null;
    }
    
    // 检查是否将军
    isInCheck(color) {
        const general = this.findGeneral(color);
        if (!general) {
            return false; // 将/帅不存在，游戏结束
        }
        
        // 检查对方所有棋子是否能攻击到将/帅
        const opponentColor = color === COLORS.RED ? COLORS.BLACK : COLORS.RED;
        
        for (let row = 0; row < BOARD_CONFIG.ROWS; row++) {
            for (let col = 0; col < BOARD_CONFIG.COLS; col++) {
                const piece = this.getPieceAt(row, col);
                if (piece && piece.color === opponentColor) {
                    // 临时移除该棋子，检查移动是否合法（避免自将）
                    this.setPieceAt(row, col, null);
                    const canAttack = piece.isValidMove(this, general.row, general.col);
                    this.setPieceAt(row, col, piece);
                    
                    if (canAttack) {
                        return true;
                    }
                }
            }
        }
        
        return false;
    }
    
    // 检查是否将死
    isCheckmated(color) {
        if (!this.isInCheck(color)) {
            return false;
        }
        
        // 检查所有棋子是否有合法移动可以解将
        for (let row = 0; row < BOARD_CONFIG.ROWS; row++) {
            for (let col = 0; col < BOARD_CONFIG.COLS; col++) {
                const piece = this.getPieceAt(row, col);
                if (piece && piece.color === color) {
                    // 获取该棋子的所有可能移动
                    const possibleMoves = piece.getPossibleMoves(this);
                    if (possibleMoves.length > 0) {
                        return false; // 有棋子可以移动解将
                    }
                }
            }
        }
        
        return true; // 所有棋子都无法解将，将死
    }
    
    // 检查是否困毙
    isStalemated(color) {
        if (this.isInCheck(color)) {
            return false; // 困毙是指没有被将军但无法移动
        }
        
        // 检查所有棋子是否有合法移动
        for (let row = 0; row < BOARD_CONFIG.ROWS; row++) {
            for (let col = 0; col < BOARD_CONFIG.COLS; col++) {
                const piece = this.getPieceAt(row, col);
                if (piece && piece.color === color) {
                    // 获取该棋子的所有可能移动
                    const possibleMoves = piece.getPossibleMoves(this);
                    if (possibleMoves.length > 0) {
                        return false; // 有棋子可以移动
                    }
                }
            }
        }
        
        return true; // 所有棋子都无法移动，困毙
    }
    
    // 检查是否和棋
    isDraw() {
        // 困毙检查
        if (this.isStalemated(COLORS.RED) || this.isStalemated(COLORS.BLACK)) {
            return true;
        }
        
        // TODO: 实现长将、长捉等和棋规则
        // TODO: 实现棋子数量不足以赢棋的和棋规则（如单炮、单马等）
        
        // 简单实现：如果连续20步没有吃子，可以判断为和棋
        if (this.moveHistory.length > 20) {
            let noCaptureMoves = 0;
            for (let i = this.moveHistory.length - 1; i >= 0; i--) {
                if (!this.moveHistory[i].capturedPiece) {
                    noCaptureMoves++;
                    if (noCaptureMoves >= 20) {
                        return true;
                    }
                } else {
                    break;
                }
            }
        }
        
        return false;
    }
    
    // 克隆棋盘
    clone() {
        const newBoard = new Board();
        newBoard.grid = [];
        
        // 深度克隆棋子
        for (let row = 0; row < BOARD_CONFIG.ROWS; row++) {
            newBoard.grid[row] = [];
            for (let col = 0; col < BOARD_CONFIG.COLS; col++) {
                const piece = this.getPieceAt(row, col);
                if (piece) {
                    const clonedPiece = createPiece(piece.type, piece.color, row, col);
                    clonedPiece.hasMoved = piece.hasMoved;
                    newBoard.grid[row][col] = clonedPiece;
                } else {
                    newBoard.grid[row][col] = null;
                }
            }
        }
        
        // 克隆历史记录
        newBoard.moveHistory = JSON.parse(JSON.stringify(this.moveHistory));
        
        return newBoard;
    }
    
    // 获取棋盘表示（用于AI评估）
    getBoardState() {
        const state = [];
        for (let row = 0; row < BOARD_CONFIG.ROWS; row++) {
            state[row] = [];
            for (let col = 0; col < BOARD_CONFIG.COLS; col++) {
                const piece = this.getPieceAt(row, col);
                if (piece) {
                    state[row][col] = {
                        type: piece.type,
                        color: piece.color
                    };
                } else {
                    state[row][col] = null;
                }
            }
        }
        return state;
    }
    
    // 绘制棋盘和棋子
    draw(ctx) {
        const { CELL_SIZE, MARGIN } = BOARD_CONFIG;
        
        // 清空画布
        ctx.clearRect(0, 0, ctx.canvas.width, ctx.canvas.height);
        
        // 绘制棋盘背景
        ctx.fillStyle = '#E8C57A';
        ctx.fillRect(MARGIN, MARGIN, 
                     CELL_SIZE * (BOARD_CONFIG.COLS - 1), 
                     CELL_SIZE * BOARD_CONFIG.ROWS);
        
        // 绘制棋盘线条
        ctx.strokeStyle = '#000';
        ctx.lineWidth = 1;
        
        // 绘制横线
        for (let i = 0; i <= BOARD_CONFIG.ROWS; i++) {
            ctx.beginPath();
            ctx.moveTo(MARGIN, MARGIN + i * CELL_SIZE);
            ctx.lineTo(MARGIN + (BOARD_CONFIG.COLS - 1) * CELL_SIZE, MARGIN + i * CELL_SIZE);
            ctx.stroke();
        }
        
        // 绘制竖线
        for (let i = 0; i < BOARD_CONFIG.COLS; i++) {
            ctx.beginPath();
            // 河界部分的竖线断开
            if (i === 0 || i === BOARD_CONFIG.COLS - 1) {
                // 两边的边线完整
                ctx.moveTo(MARGIN + i * CELL_SIZE, MARGIN);
                ctx.lineTo(MARGIN + i * CELL_SIZE, MARGIN + BOARD_CONFIG.ROWS * CELL_SIZE);
            } else {
                // 中间的线在河界断开
                ctx.moveTo(MARGIN + i * CELL_SIZE, MARGIN);
                ctx.lineTo(MARGIN + i * CELL_SIZE, MARGIN + BOARD_CONFIG.RIVER_TOP * CELL_SIZE);
                ctx.moveTo(MARGIN + i * CELL_SIZE, MARGIN + BOARD_CONFIG.RIVER_BOTTOM * CELL_SIZE);
                ctx.lineTo(MARGIN + i * CELL_SIZE, MARGIN + BOARD_CONFIG.ROWS * CELL_SIZE);
            }
            ctx.stroke();
        }
        
        // 绘制河界
        ctx.font = '24px Microsoft YaHei';
        ctx.fillStyle = '#8B0000';
        ctx.textAlign = 'center';
        ctx.fillText('楚 河', MARGIN + (BOARD_CONFIG.COLS - 1) * CELL_SIZE / 2 - CELL_SIZE, 
                     MARGIN + (BOARD_CONFIG.RIVER_TOP + 0.5) * CELL_SIZE);
        ctx.fillText('汉 界', MARGIN + (BOARD_CONFIG.COLS - 1) * CELL_SIZE / 2 + CELL_SIZE, 
                     MARGIN + (BOARD_CONFIG.RIVER_TOP + 0.5) * CELL_SIZE);
        
        // 绘制九宫格斜线
        // 红方九宫格
        ctx.beginPath();
        ctx.moveTo(MARGIN + BOARD_CONFIG.PALACE_LEFT * CELL_SIZE, MARGIN + BOARD_CONFIG.RED_PALACE_TOP * CELL_SIZE);
        ctx.lineTo(MARGIN + BOARD_CONFIG.PALACE_RIGHT * CELL_SIZE, MARGIN + BOARD_CONFIG.RED_PALACE_BOTTOM * CELL_SIZE);
        ctx.moveTo(MARGIN + BOARD_CONFIG.PALACE_RIGHT * CELL_SIZE, MARGIN + BOARD_CONFIG.RED_PALACE_TOP * CELL_SIZE);
        ctx.lineTo(MARGIN + BOARD_CONFIG.PALACE_LEFT * CELL_SIZE, MARGIN + BOARD_CONFIG.RED_PALACE_BOTTOM * CELL_SIZE);
        ctx.stroke();
        
        // 黑方九宫格
        ctx.beginPath();
        ctx.moveTo(MARGIN + BOARD_CONFIG.PALACE_LEFT * CELL_SIZE, MARGIN + BOARD_CONFIG.BLACK_PALACE_TOP * CELL_SIZE);
        ctx.lineTo(MARGIN + BOARD_CONFIG.PALACE_RIGHT * CELL_SIZE, MARGIN + BOARD_CONFIG.BLACK_PALACE_BOTTOM * CELL_SIZE);
        ctx.moveTo(MARGIN + BOARD_CONFIG.PALACE_RIGHT * CELL_SIZE, MARGIN + BOARD_CONFIG.BLACK_PALACE_TOP * CELL_SIZE);
        ctx.lineTo(MARGIN + BOARD_CONFIG.PALACE_LEFT * CELL_SIZE, MARGIN + BOARD_CONFIG.BLACK_PALACE_BOTTOM * CELL_SIZE);
        ctx.stroke();
        
        // 绘制棋子
        for (let row = 0; row < BOARD_CONFIG.ROWS; row++) {
            for (let col = 0; col < BOARD_CONFIG.COLS; col++) {
                const piece = this.getPieceAt(row, col);
                if (piece) {
                    this.drawPiece(ctx, piece, row, col);
                }
            }
        }
    }
    
    // 绘制单个棋子
    drawPiece(ctx, piece, row, col) {
        const { CELL_SIZE, MARGIN } = BOARD_CONFIG;
        const x = MARGIN + col * CELL_SIZE;
        const y = MARGIN + row * CELL_SIZE;
        const radius = CELL_SIZE * 0.4;
        
        // 绘制棋子底色
        ctx.fillStyle = piece.color === COLORS.RED ? '#F8D7DA' : '#343A40';
        ctx.beginPath();
        ctx.arc(x, y, radius, 0, Math.PI * 2);
        ctx.fill();
        
        // 绘制棋子边框
        ctx.strokeStyle = '#000';
        ctx.lineWidth = 2;
        ctx.stroke();
        
        // 绘制棋子文字
        ctx.font = 'bold 28px Microsoft YaHei';
        ctx.fillStyle = piece.color === COLORS.RED ? '#8B0000' : '#fff';
        ctx.textAlign = 'center';
        ctx.textBaseline = 'middle';
        ctx.fillText(piece.getChineseName(), x, y);
    }
    
    // 绘制选中状态
    drawSelectedPiece(ctx, row, col) {
        const { CELL_SIZE, MARGIN } = BOARD_CONFIG;
        const x = MARGIN + col * CELL_SIZE;
        const y = MARGIN + row * CELL_SIZE;
        const radius = CELL_SIZE * 0.45;
        
        // 绘制选中高亮
        ctx.strokeStyle = '#FFD700';
        ctx.lineWidth = 3;
        ctx.beginPath();
        ctx.arc(x, y, radius, 0, Math.PI * 2);
        ctx.stroke();
    }
    
    // 绘制可能的移动位置
    drawPossibleMoves(ctx, possibleMoves) {
        const { CELL_SIZE, MARGIN } = BOARD_CONFIG;
        
        possibleMoves.forEach(move => {
            const x = MARGIN + move.col * CELL_SIZE;
            const y = MARGIN + move.row * CELL_SIZE;
            const radius = CELL_SIZE * 0.2;
            
            ctx.fillStyle = 'rgba(255, 215, 0, 0.5)';
            ctx.beginPath();
            ctx.arc(x, y, radius, 0, Math.PI * 2);
            ctx.fill();
        });
    }
    
    // 将坐标转换为棋盘位置
    coordinatesToBoard(x, y) {
        const { CELL_SIZE, MARGIN } = BOARD_CONFIG;
        const col = Math.round((x - MARGIN) / CELL_SIZE);
        const row = Math.round((y - MARGIN) / CELL_SIZE);
        
        if (row >= 0 && row < BOARD_CONFIG.ROWS && col >= 0 && col < BOARD_CONFIG.COLS) {
            return { row, col };
        }
        return null;
    }
}